﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Text;
using ESRI.ArcGIS.Geodatabase;

namespace Bes.Swsp.ToolBox
{
  internal class ToolBoxSettings : IDisposable, INotifyPropertyChanged
  {
    private IGeometricNetwork _pipeNetwork;
    private IFeatureClass _catchmentClass;
    private IRaster _flowDirRaster;
    private IRaster _flowAccRaster;
    private IFeatureClass _nodesClass;
    private IFeatureClass _conveyanceClass;
    private double _flowAccThreshold;
    private bool _includeTerminalFlow;
    private IRaster _localAccumulationRaster;

    private bool _disposed = false;

    public ToolBoxSettings()
    {
    }

    ~ToolBoxSettings()
    {
      Dispose(false);
    }

    #region IDisposable Members

    public void Dispose()
    {
      this.Dispose(true);
      GC.SuppressFinalize(this);
    }

    #endregion

    private void Dispose(bool disposing)
    {
      if (!_disposed)
      {
        if (disposing)
        {
          // Managed classes
        }

        // Unmanaged classes
        ComUtility.ReleaseComObject(_pipeNetwork);
        _pipeNetwork = null;
        ComUtility.ReleaseComObject(_catchmentClass);
        _catchmentClass = null;
        ComUtility.ReleaseComObject(_flowDirRaster);
        _flowDirRaster = null;
        ComUtility.ReleaseComObject(_flowAccRaster);
        _flowAccRaster = null;
        ComUtility.ReleaseComObject(_nodesClass);
        _nodesClass = null;
        ComUtility.ReleaseComObject(_conveyanceClass);
        _conveyanceClass = null;
        ComUtility.ReleaseComObject(_localAccumulationRaster);
        _localAccumulationRaster = null;

        _disposed = true;
      }
    }

    public IGeometricNetwork PipeNetwork
    {
      get
      {
        return _pipeNetwork;
      }

      set
      {
        if (value != _pipeNetwork)
        {
          ComUtility.ReleaseComObject(_pipeNetwork);
          _pipeNetwork = value;
          ComUtility.AddReference(_pipeNetwork);
          OnPropertyChanged(new PropertyChangedEventArgs("PipeNetwork"));
        }
      }
    }

    public IFeatureClass CatchmentFeatureClass
    {
      get
      {
        return _catchmentClass;
      }

      set
      {
        if (value != _catchmentClass)
        {
          ComUtility.ReleaseComObject(_catchmentClass);
          _catchmentClass = value;
          ComUtility.AddReference(_catchmentClass);
          OnPropertyChanged(new PropertyChangedEventArgs("CatchmentFeatureClass"));
        }
      }
    }

    public IRaster FlowDirectionRaster
    {
      get
      {
        return _flowDirRaster;
      }

      set
      {
        if (value != _flowDirRaster)
        {
          ComUtility.ReleaseComObject(_flowDirRaster);
          _flowDirRaster = value;
          ComUtility.AddReference(_flowDirRaster);
          OnPropertyChanged(new PropertyChangedEventArgs("FlowDirectionRaster"));
        }
      }
    }

    public IRaster RunoffRaster
    {
      get
      {
        return _flowAccRaster;
      }

      set
      {
        if (value != _flowAccRaster)
        {
          ComUtility.ReleaseComObject(_flowAccRaster);
          _flowAccRaster = value;
          ComUtility.AddReference(_flowAccRaster);
          OnPropertyChanged(new PropertyChangedEventArgs("FlowAccumulationRaster"));
        }
      }
    }

    public IFeatureClass StormNodesFeatureClass
    {
      get
      {
        return _nodesClass;
      }

      set
      {
        if (value != _nodesClass)
        {
          ComUtility.ReleaseComObject(_nodesClass);
          _nodesClass = value;
          ComUtility.AddReference(_nodesClass);
          OnPropertyChanged(new PropertyChangedEventArgs("StormNodesFeatureClass"));
        }
      }
    }

    public IFeatureClass StormConveyanceFeatureClass
    {
      get
      {
        return _conveyanceClass;
      }

      set
      {
        if (value != _conveyanceClass)
        {
          ComUtility.ReleaseComObject(_conveyanceClass);
          _conveyanceClass = value;
          ComUtility.AddReference(_conveyanceClass);
          OnPropertyChanged(new PropertyChangedEventArgs("StormConveyanceFeatureClass"));
        }
      }
    }

    public double FlowAccumulationThreshold
    {
      get
      {
        return _flowAccThreshold;
      }

      set
      {
        if(value != _flowAccThreshold)
        {
          _flowAccThreshold = value;
          OnPropertyChanged(new PropertyChangedEventArgs("FlowAccumulationThreshold"));
        }
      }
    }

    public bool IncludeTerminalFlow
    {
      get
      {
        return _includeTerminalFlow;
      }

      set
      {
        if (value != _includeTerminalFlow)
        {
          _includeTerminalFlow = value;
          OnPropertyChanged(new PropertyChangedEventArgs("IncludeTerminalFlow"));
        }
      }
    }

    public IRaster AccumulationRaster
    {
      get
      {
        return _localAccumulationRaster;
      }

      set
      {
        if (value != _localAccumulationRaster)
        {
          ComUtility.ReleaseComObject(_localAccumulationRaster);
          _localAccumulationRaster = value;
          ComUtility.AddReference(_localAccumulationRaster);
          OnPropertyChanged(new PropertyChangedEventArgs("LocalAccumulationRaster"));
        }
      }
    }

    #region INotifyPropertyChanged Members

    public event PropertyChangedEventHandler PropertyChanged;

    protected void OnPropertyChanged(PropertyChangedEventArgs e)
    {
      if (PropertyChanged != null)
        PropertyChanged(this, e);
    }

    #endregion
  }
}
